<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">
<html>
 <head>
  <meta http-equiv="content-type" content="text/html; charset=UTF-8">
  <title>Session 上传进度</title>
<link media="all" rel="stylesheet" type="text/css" href="styles/03e73060321a0a848018724a6c83de7f-theme-base.css" />
<link media="all" rel="stylesheet" type="text/css" href="styles/03e73060321a0a848018724a6c83de7f-theme-medium.css" />

 </head>
 <body class="docs"><div class="navbar navbar-fixed-top">
  <div class="navbar-inner clearfix">
    <ul class="nav" style="width: 100%">
      <li style="float: left;"><a href="session.customhandler.html">« 自定义会话管理器</a></li>
      <li style="float: right;"><a href="session.security.html">会话和安全 »</a></li>
    </ul>
  </div>
</div>
<div id="breadcrumbs" class="clearfix">
  <ul class="breadcrumbs-container">
    <li><a href="index.html">PHP Manual</a></li>
    <li><a href="book.session.html">Sessions</a></li>
    <li>Session 上传进度</li>
  </ul>
</div>
<div id="layout">
  <div id="layout-content"><div id="session.upload-progress" class="chapter">
 <h1>Session 上传进度</h1>


 <blockquote class="note"><p><strong class="note">注意</strong>: 
  <span class="simpara">
   此特性自 PHP 5.4.0 后可用。
  </span>
 </p></blockquote>

 <p class="para">
  当
  <a href="session.configuration.html#ini.session.upload-progress.enabled" class="link">session.upload_progress.enabled</a>
  INI 选项开启时，PHP 能够在每一个文件上传时监测上传进度。
  这个信息对上传请求自身并没有什么帮助，但在文件上传时应用可以发送一个POST请求到终端（例如通过<abbr>XHR</abbr>）来检查这个状态
 </p>
 <p class="para">
  当一个上传在处理中，同时POST一个与INI中设置的<a href="session.configuration.html#ini.session.upload-progress.name" class="link">session.upload_progress.name</a>同名变量时，上传进度可以在<var class="varname"><a href="reserved.variables.session.html" class="classname">$_SESSION</a></var>中获得。
  当PHP检测到这种POST请求时，它会在<var class="varname"><a href="reserved.variables.session.html" class="classname">$_SESSION</a></var>中添加一组数据, 索引是
  <a href="session.configuration.html#ini.session.upload-progress.prefix" class="link">session.upload_progress.prefix</a>
  与
  <a href="session.configuration.html#ini.session.upload-progress.name" class="link">session.upload_progress.name</a>连接在一起的值。
  通常这些键值可以通过读取INI设置来获得，例如
  <div class="informalexample">
   <div class="example-contents">
<div class="phpcode"><code><span style="color: #000000">
<span style="color: #0000BB">&lt;?php<br />$key&nbsp;</span><span style="color: #007700">=&nbsp;</span><span style="color: #0000BB">ini_get</span><span style="color: #007700">(</span><span style="color: #DD0000">"session.upload_progress.prefix"</span><span style="color: #007700">)&nbsp;.&nbsp;</span><span style="color: #0000BB">ini_get</span><span style="color: #007700">(</span><span style="color: #DD0000">"session.upload_progress.name"</span><span style="color: #007700">);<br /></span><span style="color: #0000BB">var_dump</span><span style="color: #007700">(</span><span style="color: #0000BB">$_SESSION</span><span style="color: #007700">[</span><span style="color: #0000BB">$key</span><span style="color: #007700">]);<br /></span><span style="color: #0000BB">?&gt;</span>
</span>
</code></div>
   </div>

  </div>
 </p>
 <p class="para">
  通过将<code class="literal">$_SESSION[$key][&quot;cancel_upload&quot;]</code>设置为<strong><code>true</code></strong>，还可以<em class="emphasis">取消</em>一个正在处理中的文件上传。
  当在同一个请求中上传多个文件，它仅会取消当前正在处理的文件上传和未处理的文件上传，但是不会移除那些已经完成的上传。
  当一个上传请求被这么取消时，<var class="varname"><a href="reserved.variables.files.html" class="classname">$_FILES</a></var>中的<code class="literal">error</code>将会被设置为
  <strong><code>UPLOAD_ERR_EXTENSION</code></strong>。
 </p>
 <p class="para">
  <a href="session.configuration.html#ini.session.upload-progress.freq" class="link">session.upload_progress.freq</a>
  和
  <a href="session.configuration.html#ini.session.upload-progress.min-freq" class="link">session.upload_progress.min_freq</a>
  INI选项控制了上传进度信息应该多久被重新计算一次。
  通过合理设置这两个选项的值，这个功能的开销几乎可以忽略不计。
 </p>
 <p class="para">
  <div class="example" id="example-4698">
   <p><strong>示例 #1 样例信息</strong></p>
   <div class="example-contents"><p>
    一个上传进度数组的结构的例子
   </p></div>
   <div class="example-contents">
<div class="htmlcode"><pre class="htmlcode">&lt;form action=&quot;upload.php&quot; method=&quot;POST&quot; enctype=&quot;multipart/form-data&quot;&gt;
 &lt;input type=&quot;hidden&quot; name=&quot;&lt;?php echo ini_get(&quot;session.upload_progress.name&quot;); ?&gt;&quot; value=&quot;123&quot; /&gt;
 &lt;input type=&quot;file&quot; name=&quot;file1&quot; /&gt;
 &lt;input type=&quot;file&quot; name=&quot;file2&quot; /&gt;
 &lt;input type=&quot;submit&quot; /&gt;
&lt;/form&gt;</pre>
</div>
   </div>

   <div class="example-contents"><p>
    在session中存放的数据看上去是这样子的：
   </p></div>
   <div class="example-contents">
<div class="phpcode"><code><span style="color: #000000">
<span style="color: #0000BB">&lt;?php<br />$_SESSION</span><span style="color: #007700">[</span><span style="color: #DD0000">"upload_progress_123"</span><span style="color: #007700">]&nbsp;=&nbsp;array(<br />&nbsp;</span><span style="color: #DD0000">"start_time"&nbsp;</span><span style="color: #007700">=&gt;&nbsp;</span><span style="color: #0000BB">1234567890</span><span style="color: #007700">,&nbsp;&nbsp;&nbsp;</span><span style="color: #FF8000">//&nbsp;The&nbsp;request&nbsp;time<br />&nbsp;</span><span style="color: #DD0000">"content_length"&nbsp;</span><span style="color: #007700">=&gt;&nbsp;</span><span style="color: #0000BB">57343257</span><span style="color: #007700">,&nbsp;</span><span style="color: #FF8000">//&nbsp;POST&nbsp;content&nbsp;length<br />&nbsp;</span><span style="color: #DD0000">"bytes_processed"&nbsp;</span><span style="color: #007700">=&gt;&nbsp;</span><span style="color: #0000BB">453489</span><span style="color: #007700">,&nbsp;&nbsp;</span><span style="color: #FF8000">//&nbsp;Amount&nbsp;of&nbsp;bytes&nbsp;received&nbsp;and&nbsp;processed<br />&nbsp;</span><span style="color: #DD0000">"done"&nbsp;</span><span style="color: #007700">=&gt;&nbsp;</span><span style="color: #0000BB">false</span><span style="color: #007700">,&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #FF8000">//&nbsp;true&nbsp;when&nbsp;the&nbsp;POST&nbsp;handler&nbsp;has&nbsp;finished,&nbsp;successfully&nbsp;or&nbsp;not<br />&nbsp;</span><span style="color: #DD0000">"files"&nbsp;</span><span style="color: #007700">=&gt;&nbsp;array(<br />&nbsp;&nbsp;</span><span style="color: #0000BB">0&nbsp;</span><span style="color: #007700">=&gt;&nbsp;array(<br />&nbsp;&nbsp;&nbsp;</span><span style="color: #DD0000">"field_name"&nbsp;</span><span style="color: #007700">=&gt;&nbsp;</span><span style="color: #DD0000">"file1"</span><span style="color: #007700">,&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #FF8000">//&nbsp;Name&nbsp;of&nbsp;the&nbsp;&lt;input/&gt;&nbsp;field<br />&nbsp;&nbsp;&nbsp;//&nbsp;The&nbsp;following&nbsp;3&nbsp;elements&nbsp;equals&nbsp;those&nbsp;in&nbsp;$_FILES<br />&nbsp;&nbsp;&nbsp;</span><span style="color: #DD0000">"name"&nbsp;</span><span style="color: #007700">=&gt;&nbsp;</span><span style="color: #DD0000">"foo.avi"</span><span style="color: #007700">,<br />&nbsp;&nbsp;&nbsp;</span><span style="color: #DD0000">"tmp_name"&nbsp;</span><span style="color: #007700">=&gt;&nbsp;</span><span style="color: #DD0000">"/tmp/phpxxxxxx"</span><span style="color: #007700">,<br />&nbsp;&nbsp;&nbsp;</span><span style="color: #DD0000">"error"&nbsp;</span><span style="color: #007700">=&gt;&nbsp;</span><span style="color: #0000BB">0</span><span style="color: #007700">,<br />&nbsp;&nbsp;&nbsp;</span><span style="color: #DD0000">"done"&nbsp;</span><span style="color: #007700">=&gt;&nbsp;</span><span style="color: #0000BB">true</span><span style="color: #007700">,&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #FF8000">//&nbsp;True&nbsp;when&nbsp;the&nbsp;POST&nbsp;handler&nbsp;has&nbsp;finished&nbsp;handling&nbsp;this&nbsp;file<br />&nbsp;&nbsp;&nbsp;</span><span style="color: #DD0000">"start_time"&nbsp;</span><span style="color: #007700">=&gt;&nbsp;</span><span style="color: #0000BB">1234567890</span><span style="color: #007700">,&nbsp;&nbsp;&nbsp;&nbsp;</span><span style="color: #FF8000">//&nbsp;When&nbsp;this&nbsp;file&nbsp;has&nbsp;started&nbsp;to&nbsp;be&nbsp;processed<br />&nbsp;&nbsp;&nbsp;</span><span style="color: #DD0000">"bytes_processed"&nbsp;</span><span style="color: #007700">=&gt;&nbsp;</span><span style="color: #0000BB">57343250</span><span style="color: #007700">,&nbsp;</span><span style="color: #FF8000">//&nbsp;Amount&nbsp;of&nbsp;bytes&nbsp;received&nbsp;and&nbsp;processed&nbsp;for&nbsp;this&nbsp;file<br />&nbsp;&nbsp;</span><span style="color: #007700">),<br />&nbsp;&nbsp;</span><span style="color: #FF8000">//&nbsp;An&nbsp;other&nbsp;file,&nbsp;not&nbsp;finished&nbsp;uploading,&nbsp;in&nbsp;the&nbsp;same&nbsp;request<br />&nbsp;&nbsp;</span><span style="color: #0000BB">1&nbsp;</span><span style="color: #007700">=&gt;&nbsp;array(<br />&nbsp;&nbsp;&nbsp;</span><span style="color: #DD0000">"field_name"&nbsp;</span><span style="color: #007700">=&gt;&nbsp;</span><span style="color: #DD0000">"file2"</span><span style="color: #007700">,<br />&nbsp;&nbsp;&nbsp;</span><span style="color: #DD0000">"name"&nbsp;</span><span style="color: #007700">=&gt;&nbsp;</span><span style="color: #DD0000">"bar.avi"</span><span style="color: #007700">,<br />&nbsp;&nbsp;&nbsp;</span><span style="color: #DD0000">"tmp_name"&nbsp;</span><span style="color: #007700">=&gt;&nbsp;</span><span style="color: #0000BB">NULL</span><span style="color: #007700">,<br />&nbsp;&nbsp;&nbsp;</span><span style="color: #DD0000">"error"&nbsp;</span><span style="color: #007700">=&gt;&nbsp;</span><span style="color: #0000BB">0</span><span style="color: #007700">,<br />&nbsp;&nbsp;&nbsp;</span><span style="color: #DD0000">"done"&nbsp;</span><span style="color: #007700">=&gt;&nbsp;</span><span style="color: #0000BB">false</span><span style="color: #007700">,<br />&nbsp;&nbsp;&nbsp;</span><span style="color: #DD0000">"start_time"&nbsp;</span><span style="color: #007700">=&gt;&nbsp;</span><span style="color: #0000BB">1234567899</span><span style="color: #007700">,<br />&nbsp;&nbsp;&nbsp;</span><span style="color: #DD0000">"bytes_processed"&nbsp;</span><span style="color: #007700">=&gt;&nbsp;</span><span style="color: #0000BB">54554</span><span style="color: #007700">,<br />&nbsp;&nbsp;),<br />&nbsp;)<br />);</span>
</span>
</code></div>
   </div>

  </div>
 </p>
 <div class="warning"><strong class="warning">警告</strong>
  <p class="para">
   为了使这个正常工作，web服务器的请求缓冲区需要禁用，否则 PHP可能仅当文件完全上传完成时才能收到文件上传请求。
   已知会缓冲这种大请求的程序有Nginx。
  </p>
 </div>
 <div class="caution"><strong class="caution">警告</strong>
  <p class="para">
   这个进度信息是在任意脚本被执行前写入session的，因此通过
   <span class="function"><a href="function.ini-set.html" class="function">ini_set()</a></span>或<span class="function"><a href="function.session-name.html" class="function">session_name()</a></span>修改session名将会导致一个没有上传进度信息的session。
  </p>
 </div>
</div>
</div></div></body></html>